package com.killer.goods.service.impl;

import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.killer.common.entity.Result;
import com.killer.db.service.impl.BaseServiceImpl;
import com.killer.goods.entity.*;
import com.killer.goods.enums.SpuStatusEnums;
import com.killer.goods.mapper.SpuMapper;
import com.killer.goods.service.*;
import com.killer.leaf.feign.SnowFlakeClient;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * <p>
 * 标准产品单位表 服务实现类
 * </p>
 *
 * @author killer
 * @since 2021-08-29
 */
@Service
public class SpuServiceImpl extends BaseServiceImpl<SpuMapper, Spu> implements ISpuService {

    @Autowired
    private SnowFlakeClient snowFlakeClient;
    @Autowired
    private IBrandService brandService;
    @Autowired
    private ISkuService skuService;
    @Autowired
    private ICategoryService categoryService;
    @Autowired
    private ICategoryBrandService categoryBrandService;

    @Override
    public List<Spu> batchGetMarketableSpu(Long startId) {
        return baseMapper.batchGetMarketableSpu(startId);
    }

    @Override
    protected LambdaQueryWrapper<Spu> createQueryWrapper(Map<String, Object> searchMap) {
        LambdaQueryWrapper<Spu> queryWrapper = Wrappers.lambdaQuery(Spu.class);
        if (searchMap != null) {
            queryWrapper.eq(searchMap.get("isMarketable") != null, Spu::getIsMarketable, searchMap.get("isMarketable"));
            queryWrapper.eq(searchMap.get("status") != null, Spu::getStatus, searchMap.get("status"));
        }
        return queryWrapper;
    }

    @Override
    @Transactional
    public void addGoods(Goods goods) {
        Result<Long> result = snowFlakeClient.getId();
        if (result == null) {
            throw new RuntimeException("获取分布式id失败");
        }
        long id=result.getData();
        //设置spuId
        Spu spu = goods.getSpu();
        spu.setId(id);
        //保存spu
        super.save(spu);
        //保存skuList
        saveSkuList(goods);
    }

    @Override
    public Goods findGoodsById(Long id) {
        //查询spu
        Spu spu = super.getById(id);
        if (spu == null) {
            throw new RuntimeException("该商品id:{}"+id+"对应的商品不存在");
        }
        //查询sku
        Map<String, Object> params = new HashMap<>();
        params.put("spuId", id);
        List<Sku> skuList = skuService.search(params);
        Goods goods=new Goods();
        goods.setSpu(spu);
        goods.setSkuList(skuList);
        return goods;
    }

    @Override
    public void updateGoods(Goods goods) {
        //取出spu部分
        Spu spu=goods.getSpu();
        if (spu.getId() == null) {
            throw new RuntimeException("请选择需要更新的商品");
        }
        //更新spu
        super.updateById(spu);
        //删除原有的sku列表
        removeOldSku(spu);
        //保存新的sku列表
        saveSkuList(goods);
    }

    @Override
    public void autit(Long id) {
        Spu spu = super.getById(id);
        if (spu == null) {
            throw new RuntimeException("商品不存在或已被删除");
        }
        spu.setStatus(SpuStatusEnums.AUDIT.getCode());
        super.updateById(spu);
    }

    @Override
    public void pull(Long id) {
        Spu spu = super.getById(id);
        if (spu == null) {
            throw new RuntimeException("该商品不存在或已删除");
        }
        spu.setIsMarketable(false);
        super.updateById(spu);
    }

    @Override
    public void put(Long id) {
        Spu spu = super.getById(id);
        if (spu == null) {
            throw new RuntimeException("该商品不存在或已删除");
        }

        if (spu.getStatus() == SpuStatusEnums.UNUNADIT.getCode()) {
            throw new RuntimeException("商品未审核，不能上架");
        }
        spu.setIsMarketable(true);
        super.updateById(spu);
    }

    private void removeOldSku(Spu spu) {
        Map<String,Object> params=new HashMap<>();
        params.put("spu_id", spu.getId());
        skuService.removeByMap(params);
    }

    private void saveSkuList(Goods goods) {
        //获取sku对象
        List<Sku> skuList = goods.getSkuList();
        if (CollectionUtils.isEmpty(skuList)) {
            return;
        }
        //获取spu对象
        Spu spu = goods.getSpu();
        //获取品牌对象
        Brand brand = brandService.getById(spu.getBrandId());
        //获取3级分类对象
        Category category = categoryService.getById(spu.getCategory3Id());
        //添加分类品牌
        addCategoryBrandIfNecessary(spu);
        //批量获取id
        List<Long> idList = batchGetIds(skuList);
        //遍历sku进行赋值
        for (int i=0;i<skuList.size();i++) {
            Sku sku = skuList.get(i);
            //设置主键
            sku.setId(idList.get(i));
            //设置规格
            if (StringUtils.isBlank(sku.getSpec())) {
                sku.setSpec("{}");
            }
            //设置spu名称(商品名称+sku规格)
            String name = extractSkuName(spu, sku);
            //名称
            sku.setName(name);
            //商品id
            sku.setSpuId(spu.getId());
            //商品3级分类id
            sku.setCategoryId(spu.getCategory3Id());
            if (category != null) {
                //商品3级分类名称
                sku.setCategoryName(category.getName());
            }
            if (brand != null) {
                //品牌名称
                sku.setBrandName(brand.getName());
            }
            //保存数据
            skuService.save(sku);
        }
    }

    private String extractSkuName(Spu spu, Sku sku) {
        String name = spu.getName();
        //将规格json字符串转换成map
        Map<String, String> specMap = JSONObject.parseObject(sku.getSpec(), Map.class);
        if (specMap != null) {
            for (String spec : specMap.values()) {
                name=name+" "+spec;
            }
        }
        return name;
    }

    private List<Long> batchGetIds(List<Sku> skuList) {
        Result<List<Long>> result = snowFlakeClient.getBatch(skuList.size());
        if (result == null) {
            throw new RuntimeException("批量获取分布式id异常");
        }
        return result.getData();
    }

    private void addCategoryBrandIfNecessary(Spu spu) {
        //添加分类与品牌之间的关联关系
        Map<String, Object> params = new HashMap<>();
        params.put("brandId", spu.getBrandId());
        params.put("categoryId", spu.getCategory3Id());
        Integer count = categoryBrandService.countByCondition(params);
        if (count <= 0) {
            CategoryBrand categoryBrand=new CategoryBrand();
            categoryBrand.setBrandId(spu.getBrandId());
            categoryBrand.setCategoryId(spu.getCategory3Id());
            categoryBrandService.save(categoryBrand);
            System.out.println(JSONObject.toJSONString(categoryBrand));

        }
    }
}
